package com.ciko.code.logic.db;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.text.TextUtils;

import com.ciko.code.annotations.Column;
import com.ciko.code.annotations.Except;
import com.ciko.code.logic.table.AddressBookInfoTable;
import com.ciko.code.logic.table.GroupTable;
import com.ciko.code.utils.PerferencesUtil;

import java.io.Serializable;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;


/**
 * 联系人数据库
 * @author 刘宾
 * @date 2015年12月15日 下午2:20:16
 */
public class ContactsDBHelper2
        extends
        SQLiteOpenHelper
{
	public static final int                    TYPE_INSERT              = 1;
	public static final int                    TYPE_UPDATE              = 2;
	public static final int                    TYPE_DELETE              = 3;
	public static final int                    TYPE_QUERY               = 4;
	private static ContactsDBHelper2 myInstance               = null;
	private Context                            context;
	public final static String DB = "qy_contacts.db";
	public final static int DB_VERSION = 2;

	// 可读的SQLiteDatabase对象
	private static ThreadLocal<SQLiteDatabase> sqliteDatabaseR          = new ThreadLocal<SQLiteDatabase>();
	// 可写的SQLiteDatabase对象
	private static ThreadLocal<SQLiteDatabase> sqliteDatabaseW          = new ThreadLocal<SQLiteDatabase>();


	private ContactsDBHelper2(Context context) {
		super(context, DB, null, DB_VERSION);
		this.context = context;
	}

	private void createTables(SQLiteDatabase db) {
		db.execSQL(AddressBookInfoTable.getCreateTableSQL());
		db.execSQL(GroupTable.getCreateTableSQL());
	}

	public static ContactsDBHelper2 getInstance(Context context) {
		if (myInstance == null)
		{
			myInstance = new ContactsDBHelper2(context);
		}
		return myInstance;
	}

	@Override
	public void onCreate(SQLiteDatabase db) {
		createTables(db);
	}

	@Override
	public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
		try {
			db.beginTransaction();
			if (oldVersion < DB_VERSION) {
				update2(db);
			}
			db.setTransactionSuccessful();
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			db.endTransaction();
		}
		db.setVersion(DB_VERSION);
	}

	private void update2(SQLiteDatabase db) {
		db.execSQL("DROP TABLE IF EXISTS " + AddressBookInfoTable.table);
		db.execSQL(AddressBookInfoTable.getCreateTableSQL());
		PerferencesUtil.getInstance(context).setContactLastTimeStamp(0);
	}
	/**
	 * 获得可读的SQLiteDatabase对象
	 */
	public synchronized SQLiteDatabase getSqliteDatabaseR() {
		SQLiteDatabase dbR = sqliteDatabaseR.get();
		if (null == dbR || !dbR.isOpen())
		{
			dbR = getReadableDatabase();
			sqliteDatabaseR.set(dbR);
		}
		return dbR;
	}

	/**
	 * 关闭可读的SQLiteDatabase对象
	 */
	public void closeSqliteDatabaseR() {
		SQLiteDatabase dbR = sqliteDatabaseR.get();
		if (null != dbR || dbR.isOpen())
		{
			dbR.close();
			sqliteDatabaseR.set(null);
		}
	}

	/**
	 * 获得可写的SQLiteDatabase对象
	 */
	public synchronized SQLiteDatabase getSqliteDatabaseW() {
		SQLiteDatabase dbW = sqliteDatabaseW.get();
		if (null == dbW || !dbW.isOpen())
		{
			dbW = getWritableDatabase();
			sqliteDatabaseW.set(dbW);
		}
		return dbW;
	}

	/**
	 * 关闭可写的SQLiteDatabase对象
	 */
	public void closeSqliteDatabaseW() {
		SQLiteDatabase dbW = sqliteDatabaseW.get();
		if (null != dbW || dbW.isOpen())
		{
			dbW.close();
			sqliteDatabaseW.set(null);
		}
	}

	/** 关闭游标 */
	public void closeCursor(Cursor c) {
		if (c != null)
		{
			c.close();
			c = null;
		}
	}

	/**
	 * 游标 --转换为 --> Object
	 *
	 * @param bean
	 * @param c
	 * @throws IllegalArgumentException
	 * @throws IllegalAccessException
	 */
	public void setObject(Object bean, Cursor c) throws IllegalArgumentException, IllegalAccessException {
		for (Field f : bean.getClass().getDeclaredFields())
		{
			f.setAccessible(true);
			String columnName = f.getName();
			int columnIndex = c.getColumnIndex(columnName);
			if (columnIndex == -1)
			{
				continue;
			}
			if (f.getGenericType() == Long.class || f.getGenericType() == long.class)
			{
				f.set(bean, c.getLong(columnIndex));
			}
			else if (f.getGenericType() == String.class)
			{
				String s = c.getString(columnIndex);
				f.set(bean, TextUtils.isEmpty(s) ? "" : s);
			}
			else if (f.getGenericType() == Double.class || f.getGenericType() == double.class)
			{
				f.set(bean, c.getDouble(columnIndex));
			}
			else if (f.getGenericType() == Integer.class || f.getGenericType() == int.class)
			{
				f.set(bean, c.getInt(columnIndex));
			}
			else if (f.getGenericType() == Float.class || f.getGenericType() == float.class)
			{
				f.set(bean, c.getFloat(columnIndex));
			}
			else if (f.getGenericType() == Short.class || f.getGenericType() == short.class)
			{
				f.set(bean, c.getShort(columnIndex));
			}
			else if (f.getGenericType() == Byte[].class || f.getGenericType() == byte[].class)
			{
				f.set(bean, c.getBlob(columnIndex));
			}
			else
			{ //TODO 未知类型
				f.set(bean, c.getString(columnIndex));
			}
		}
	}

	/**
	 * 游标 --转换为 --> 给定类型的对象
	 *
	 * @param clazz
	 * @param c
	 * @return
	 * @throws InstantiationException
	 * @throws IllegalAccessException
	 */
	public <T extends Serializable> T getObject(Class<T> clazz, Cursor c) throws InstantiationException, IllegalAccessException {
		T t = (T) clazz.newInstance();
		setObject(t, c);
		return t;
	}

	/**
	 * 对象 --转换为 --> ContentValues
	 *
	 * @param bean
	 * @return
	 * @throws IllegalArgumentException
	 * @throws IllegalAccessException
	 */
	public ContentValues getContentValues(int type, Object bean) throws IllegalArgumentException, IllegalAccessException {
		ContentValues values = new ContentValues();
		for (Field f : bean.getClass().getDeclaredFields())
		{
			f.setAccessible(true);
			if (!Modifier.isStatic(f.getModifiers()) && f.getAnnotation(Except.class) == null)
			{
				Column c = f.getAnnotation(Column.class);
				Object value = f.get(bean);
				String name = c == null ? f.getName() : (TextUtils.isEmpty(c.columnName()) ? f.getName() : c.columnName());
				if (c != null && c.primaryKey() == true)
				{
					if (type == TYPE_INSERT) values.put(name, (String) null);
				}
				else if (value instanceof Long)
				{
					values.put(name, (Long) value);
				}
				else if (value instanceof String)
				{
					values.put(name, (String) value);
				}
				else if (value instanceof Double)
				{
					values.put(name, (Double) value);
				}
				else if (value instanceof Integer)
				{
					values.put(name, (Integer) value);
				}
				else if (value instanceof Float)
				{
					values.put(name, (Float) value);
				}
				else if (value instanceof Short)
				{
					values.put(name, (Short) value);
				}
				else if (value instanceof Byte)
				{
					values.put(name, (Byte) value);
				}
				else if (value instanceof Byte[])
				{
					values.put(name, (byte[]) value);
				}
				else
				{ //TODO 未知类型
					values.put(name, value != null ? value.toString() : "");
				}
			}
		}
		return values;
	}

	/**
	 * 得到数据库表的列名
	 *
	 * @param db
	 * @param tableName
	 * @return
	 */
	protected String getColumnNames(SQLiteDatabase db, String tableName) {
		//String[] columnNames = null;
		Cursor c = null;
		String result = "";
		try
		{
			c = db.rawQuery("PRAGMA table_info(" + tableName + ")", null);
			if (null != c)
			{
				int columnIndex = c.getColumnIndex("name");
				if (-1 == columnIndex) { return null; }

				int index = 0;
				//columnNames = new String[c.getCount()];
				for (c.moveToFirst(); !c.isAfterLast(); c.moveToNext())
				{
					if (index == 0)
					{
						result = c.getString(columnIndex);
					}
					else
					{
						result = result + "," + c.getString(columnIndex);
					}
					//columnNames[index] = c.getString(columnIndex);
					index++;
				}
			}
		}
		catch (Exception e)
		{
			e.printStackTrace();
		}
		finally
		{
			c.close();
			c = null;
		}
		//return columnNames;
		return result;
	}
}
